"""
author: runyu.ma
"""

from ..core.dslc_symbol_table import SymbolTable
from ..core.dslc_parser import BinaryOp, BlockOp, ASTNode, Number, Identifier
from ..interpret import evaluation


def builtin_insta_pass(stab: SymbolTable, top: BinaryOp):
    if top.op != '!':
        raise ValueError("not CALL")
    if top.l.name == 'irand':
        return __replace_irand(stab, top.r)
    if top.l.name == 'ilength':
        return __replace_ilength(stab, top.r)
    return top
    

def __replace_irand(stab: SymbolTable, top: ASTNode):
    '''替换irand'''
    if not isinstance(top, BlockOp):
        raise ValueError("not BlockOp")
    print(top)
    print(stab.lsvisiable())
    startval = evaluation(stab, top.oplist[0])
    stopval = evaluation(stab, top.oplist[1])
    print(startval)
    raise
    oplist = []
    oplist.append(Number(1))
    oplist.append(Number(2))
    oplist.append(Number(3))
    return BlockOp(oplist)


def __replace_ilength(stab: SymbolTable, top: ASTNode):
    '''替换求长度'''  
    if isinstance(top, BlockOp):
        return Number(len(top.oplist))
    if isinstance(top, Identifier):
        isym = stab.lookup(top.name)
        if isym:
            if isinstance(top.parent.parent, BinaryOp) and top.parent.parent.op == '=':
                isym2 = stab.lookup(top.parent.parent.l.name)
                if isym2:
                    isym2.info['ival'] = len(isym.info['astobj'].oplist)
                else:
                    stab.add(top.parent.parent.l.name, {'ival': len(isym.info['astobj'].oplist)})
            return Number(len(isym.info['astobj'].oplist))
        else:
            print("ILENGTH corrupt: skip {}".format(str(top)))
            return top.parent
    raise ValueError("not BlockOp; not Identifier")
